home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
HPAVC
/
HPAVC CD-ROM.iso
/
WD_SRC.ZIP
/
SOURCE
/
DOOM_TEX.CPP
< prev
next >
Wrap
C/C++ Source or Header
|
1995-01-12
|
7KB
|
261 lines
#include "..\Source\LastWolf.hpp"
MPointerArray pPNames;
BOOL InitDoomTex( MFile *pWadFile, DWORD directoryPos )
{
DirEntry dirPNames;
WORD nPNames, i;
// Load in the whole PNAMES lookup table.
GetDirEntry( pWadFile, "PNAMES", directoryPos, &dirPNames );
pWadFile->fio_Seek( dirPNames.resPos );
pWadFile->fio_Read( &nPNames, 2 );
pWadFile->fio_Seek( pWadFile->fio_GetPosition() + 2 );
pPNames.SetSize(nPNames);
for( i=0; i < nPNames; i++ )
{
pPNames.Set( i, new char[8] );
pWadFile->fio_Read( pPNames.Get(i), 8 );
}
return TRUE;
}
BOOL UnInitDoomTex()
{
WORD i;
for( i=0; i < pPNames.NumElements(); i++ )
delete pPNames.Get(i);
return TRUE;
}
TextureID LoadSidedefTexture( DoomSidedef *pSidedef, MFile *pWadFile, DWORD directoryPos )
{
TextureID idTexture;
Texture *pNewTexture;
DWORD texturePos;
char terminatedTextureName[50];
// Handle the case where there is no texture.
if( pSidedef->normalTex[0] == '-' )
{
idTexture = BAD_TEXTURE_ID;
}
else
{
idTexture = tx_GetIDFromName( pSidedef->normalTex );
// If the the texture didn't exist, load it from pWadFile.
if( idTexture == BAD_TEXTURE_ID )
{
strncpy( terminatedTextureName, pSidedef->normalTex, 8 );
terminatedTextureName[8] = 0;
puts( terminatedTextureName );
// Create a new texture and fill in its name.
pNewTexture = tx_AddTexture( &idTexture );
strncpy( pNewTexture->textureName, pSidedef->normalTex, 8 );
texturePos = FindTexture( pWadFile, pSidedef->normalTex, directoryPos );
assert( texturePos != -1 );
ComposeTexture( pWadFile, directoryPos, texturePos, pNewTexture );
// Set the shifting and masking values here.
switch( pNewTexture->width )
{
case 32:
pNewTexture->xTextureShift = (FIXED_SHIFT - 5);
pNewTexture->xTextureMask = 31;
break;
case 64:
pNewTexture->xTextureShift = (FIXED_SHIFT - 6);
pNewTexture->xTextureMask = 63;
break;
case 128:
pNewTexture->xTextureShift = (FIXED_SHIFT - 7);
pNewTexture->xTextureMask = 127;
break;
case 256:
pNewTexture->xTextureShift = (FIXED_SHIFT - 8);
pNewTexture->xTextureMask = 255;
break;
}
}
}
return idTexture;
}
DWORD FindTexture( MFile *pWadFile, BYTE *pTexName, DWORD directoryPos )
{
DirEntry dirTexture1;
DWORD nTextures;
WORD n;
MDWordArray textureOffsets;
TextureEntry testEntry;
// Get TEXTURE1 and TEXTURE2 directory entries.
GetDirEntry( pWadFile, "TEXTURE1", directoryPos, &dirTexture1 );
// Find the texture name in TEXTURE1 .. TEXTURE2 doesn't seem to exist for Doom 2.
pWadFile->fio_Seek( dirTexture1.resPos );
pWadFile->fio_Read( &nTextures, 4 );
textureOffsets.SetSize(nTextures);
pWadFile->fio_Read( textureOffsets.GetBuffer(), nTextures*4 );
for( n=0; n < nTextures; n++ )
{
pWadFile->fio_Seek( textureOffsets.Get(n) + dirTexture1.resPos );
pWadFile->fio_Read( &testEntry, sizeof(testEntry) );
if( strncmp( testEntry.textureName, pTexName, 8 ) == 0 )
{
return textureOffsets.Get(n) + dirTexture1.resPos;
}
}
// If it gets here, it can't find it.
return -1;
}
BOOL ComposeTexture( MFile *pWadFile, DWORD directoryPos, DWORD texturePos, Texture *pNewTexture )
{
// Uses the maximum number of Patches automatically .. I was getting some
// stupid memory allocation error when I allocated them.
Patch Patches[64];
TextureEntry texEntry;
WORD i;
// Read the texture descriptor.
pWadFile->fio_Seek( texturePos );
pWadFile->fio_Read( &texEntry, sizeof(texEntry) );
// Read all the patches.
pWadFile->fio_Read( &Patches, sizeof(Patch) * texEntry.nPatchDescriptors );
// Create the actual texture space.
pNewTexture->width = texEntry.totalWidth;
pNewTexture->height = texEntry.totalHeight;
pNewTexture->pVertLines = new BYTE *[pNewTexture->width];
for( i=0; i < pNewTexture->width; i++ )
pNewTexture->pVertLines[i] = new BYTE[pNewTexture->height];
// Draw all the textures into the texture space.
for( i=0; i < texEntry.nPatchDescriptors; i++ )
PastePatch( pNewTexture, &Patches[i], pWadFile, directoryPos );
return TRUE;
}
BOOL PastePatch( Texture *pPasteTo, Patch *pPasteFrom, MFile *pWadFile, DWORD directoryPos )
{
DirEntry dirPicture;
WORD i, startExtra, endExtra;
char *patchName;
// Temporary data for the Patch.
WORD picWidth, picHeight, xOffset, yOffset;
MDWordArray columnPointers;
DWORD bufferSize, bufferPos;
BYTE *pPatchBuffer;
WORD vertStart, vertLen;
// Read in the header.
patchName = (char *)pPNames.Get( pPasteFrom->iPNamesEntry );
GetDirEntry( pWadFile, patchName, directoryPos, &dirPicture );
pWadFile->fio_Seek( dirPicture.resPos );
pWadFile->fio_Read( &picWidth, 2 );
pWadFile->fio_Read( &picHeight, 2 );
pWadFile->fio_Read( &xOffset, 2 );
pWadFile->fio_Read( &yOffset, 2 );
columnPointers.SetSize(picWidth);
pWadFile->fio_Read( columnPointers.GetBuffer(), picWidth*4 );
// Allocate a giant buffer for all the picture data (the 1024 at the end is for the last column).
bufferSize = columnPointers.Get(columnPointers.NumElements()-1) + 1024;
pPatchBuffer = new BYTE[ bufferSize ];
// Read the data into it.
pWadFile->fio_Seek( dirPicture.resPos );
pWadFile->fio_Read( pPatchBuffer, bufferSize );
// Read in the picture data and paste it on pPasteTo.
for( i=0; i < picWidth; i++ )
{
if( i + pPasteFrom->xOffset >= pPasteTo->width || i + pPasteFrom->xOffset < 0 )
continue;
bufferPos = columnPointers.Get(i);
while(1)
{
vertStart = pPatchBuffer[bufferPos];
++bufferPos;
if( vertStart == 255 )
break;
vertLen = pPatchBuffer[bufferPos];
++bufferPos;
vertStart += pPasteFrom->yOffset;
startExtra = 1;
endExtra = 1;
if( vertStart < 0 )
{
startExtra += -vertStart;
vertLen += vertStart;
vertStart = 0;
}
if( vertStart + vertLen > pPasteTo->height )
{
endExtra += (vertStart+vertLen) - pPasteTo->height;
vertLen = pPasteTo->height - vertStart;
}
// The two fio_ReadByte()'s here are just for the extra 2 bytes the WAD has for each picture.
bufferPos += startExtra;
memcpy( &pPasteTo->pVertLines[ i+pPasteFrom->xOffset ][ vertStart ], &pPatchBuffer[bufferPos], vertLen );
bufferPos += vertLen;
bufferPos += endExtra;
}
}
delete pPatchBuffer;
return TRUE;
}